import pygame
import os
import enum
import torch
import os
import numpy as np
import random
from collections import defaultdict

class Piece(enum.Enum):
    EMPTY = 0
    BLACK = 1
    WHITE = 2

class GameScreen:
    def __init__(self, game):
        self.game = game
        self.screen = game.screen
        self.width = game.width
        self.height = game.height
        self.username = game.username
        self.db_manager = game.db_manager if hasattr(game, 'db_manager') else None
        
        # 颜色定义
        self.white = (255, 255, 255)
        self.black = (0, 0, 0)
        self.gray = (230, 230, 230)
        self.light_gray = (240, 240, 240)
        self.apple_blue = (0, 122, 255)
        self.apple_light_blue = (88, 172, 255)
        self.board_color = (240, 217, 181)  # 棋盘颜色
        
        # 字体路径 
        self.font_path = 'C:\\Windows\\Fonts\\simsun.ttc'
        
        # 字体 - 调整字体大小，适应更小的信息框
        pygame.font.init()
        try:
            self.title_font = pygame.font.Font(self.font_path, 36) # 标题字体
            self.info_font = pygame.font.Font(self.font_path, 24)   # 信息字体
            self.timer_font = pygame.font.Font(self.font_path, 28)  # 计时器字体
        except:
            self.title_font = pygame.font.SysFont("simsun", 36)
            self.info_font = pygame.font.SysFont("simsun", 24)
            self.timer_font = pygame.font.SysFont("simsun", 28)
        
        # 棋盘设置 - 保持棋盘大小不变，只调整位置
        self.board_size = 15  # 15x15的棋盘
        self.cell_size = 48  # 固定棋盘格子大小
        self.board_margin = 100  # 保持边距
        
        # 计算棋盘位置，使其居中
        self.board_width = self.cell_size * (self.board_size - 1)
        self.board_x = (self.width - self.board_width) // 2 + 30 # 棋盘左上角坐标
        self.board_y = (self.height - self.board_width) // 2 + 30  # 棋盘左上角坐标
        
        # 创建棋盘区域的矩形
        self.board_rect = pygame.Rect(
            self.board_x - self.cell_size // 2, 
            self.board_y - self.cell_size // 2, 
            self.board_width + self.cell_size, 
            self.board_width + self.cell_size
        )
        
        # 棋盘矩形区域的信息
        print(f"棋盘矩形区域: x={self.board_x - self.cell_size // 2}, y={self.board_y - self.cell_size // 2}, 宽={self.board_width + self.cell_size}, 高={self.board_width + self.cell_size}")
        
        # 加载棋子图片
        self.black_piece = None
        self.white_piece = None
        try:
            black_path = os.path.join("img", "black.png")
            white_path = os.path.join("img", "white.png")
            if os.path.exists(black_path) and os.path.exists(white_path):
                self.black_piece = pygame.image.load(black_path)
                self.white_piece = pygame.image.load(white_path)
                # 调整棋子大小
                piece_size = int(self.cell_size * 0.9)
                self.black_piece = pygame.transform.scale(self.black_piece, (piece_size, piece_size))
                self.white_piece = pygame.transform.scale(self.white_piece, (piece_size, piece_size))
        except:
            pass
        
        # 加载音效
        self.down_sound = None
        self.win_sound = None
        self.lose_sound = None
        try:
            down_path = os.path.join("sound", "down.mp3")
            win_path = os.path.join("sound", "victory.mp3")
            lose_path = os.path.join("sound", "lose.mp3")
            
            if os.path.exists(down_path):
                self.down_sound = pygame.mixer.Sound(down_path)
            if os.path.exists(win_path):
                self.win_sound = pygame.mixer.Sound(win_path)
            if os.path.exists(lose_path):
                self.lose_sound = pygame.mixer.Sound(lose_path)
        except:
            pass
        
        # 游戏状态
        # 初始化棋盘
        self.board = [[Piece.EMPTY for _ in range(self.board_size)] for _ in range(self.board_size)]  # 使用Piece.EMPTY代替0
        self.current_player = Piece.BLACK  # 当前玩家   
        self.game_over = False # 游戏是否结束
        self.winner = Piece.EMPTY  # 获胜者
        self.result_recorded = False  # 是否已记录比赛结果
        
        # 游戏模式
        self.game_mode = game.game_mode  # "local", "online", "ai"
        
        # 显示游戏模式信息
        mode_info = {
            "local": "本地对战模式",
            "online": "联机对战模式",
            "ai": "AI对战模式"
        }
        self.mode_text = mode_info.get(self.game_mode, "未知模式")
        
        # 返回菜单按钮 - 调整位置和大小，使界面更协调
        self.back_button_rect = pygame.Rect(self.width - 160, 20, 140, 50)
        self.back_button_text = "返回菜单"
        
        # 悔棋按钮
        self.undo_button_rect = pygame.Rect(self.width - 160, 80, 140, 50)
        self.undo_button_text = "悔棋"
        
        # 计时器相关
        self.turn_time_limit = 30  # 每回合30秒
        self.black_time_left = self.turn_time_limit
        self.white_time_left = self.turn_time_limit
        self.last_time_update = pygame.time.get_ticks()
        
        # 悔棋相关
        self.move_history = []  # 存储落子历史 [(x, y, player), ...]
        
        # AI算法选择，默认为基于神经网络的模型
        self.ai_algorithm = "traditional"  # 可以是 "neural" 或 "traditional"
    
    def draw_piece(self, screen, x, y, piece):
        if piece == Piece.BLACK:
            if self.black_piece:
                img_rect = self.black_piece.get_rect(center=(x, y))
                screen.blit(self.black_piece, img_rect)
            else:
                pygame.draw.circle(screen, self.black, (x, y), int(self.cell_size * 0.45))
        else:
            if self.white_piece:
                img_rect = self.white_piece.get_rect(center=(x, y))
                screen.blit(self.white_piece, img_rect)
            else:
                pygame.draw.circle(screen, self.white, (x, y), int(self.cell_size * 0.45))

    def traditional_ai_move(self):
        """使用基于Threat-Space Search的传统算法实现AI落子功能"""
        if self.game_over or self.current_player != Piece.WHITE:  # 假设AI执白棋
            return
        
        try:
            # 定义五子棋中的各种威胁形态及其分数
            # 实现一个基于威胁空间搜索的AI
            board_x, board_y = self._threat_space_search()
            
            # 记录AI的落子
            self.move_history.append((board_x, board_y, self.current_player))
            
            # 更新棋盘
            self.board[board_y][board_x] = Piece.WHITE
            
            # 播放落子音效
            if self.down_sound:
                self.down_sound.play()
            
            # 重置计时器
            self.white_time_left = self.turn_time_limit
            self.last_time_update = pygame.time.get_ticks()
            
            # 检查AI是否获胜
            if self.check_win(board_x, board_y):
                self.game_over = True
                self.winner = Piece.WHITE
                if self.lose_sound:
                    self.lose_sound.play()
            else:
                # 切换到玩家回合
                self.current_player = Piece.BLACK
            
        except Exception as e:
            print(f"传统AI落子出错: {e}")
            import traceback
            traceback.print_exc()
            
            # 如果AI出错，随机选择一个合法位置
            print("使用随机落子策略作为备选")
            empty_positions = []
            for y in range(self.board_size):
                for x in range(self.board_size):
                    if self.board[y][x] == Piece.EMPTY:
                        empty_positions.append((x, y))
            
            if empty_positions:
                board_x, board_y = random.choice(empty_positions)
                
                # 记录AI的随机落子
                self.move_history.append((board_x, board_y, self.current_player))
                
                # 更新棋盘
                self.board[board_y][board_x] = Piece.WHITE
                
                # 播放落子音效
                if self.down_sound:
                    self.down_sound.play()
                
                # 重置计时器
                self.white_time_left = self.turn_time_limit
                self.last_time_update = pygame.time.get_ticks()
                
                # 检查AI是否获胜
                if self.check_win(board_x, board_y):
                    self.game_over = True
                    self.winner = Piece.WHITE
                    if self.lose_sound:
                        self.lose_sound.play()
                else:
                    # 切换到玩家回合
                    self.current_player = Piece.BLACK

    def _threat_space_search(self):
        """实现基于威胁空间搜索的算法"""
        # 棋型定义
        FIVE = 5        # 连五 (胜利)
        OPEN_FOUR = 4   # 活四 (必胜)
        FOUR = 3        # 冲四 (可能胜利)
        OPEN_THREE = 2  # 活三 (强威胁)
        THREE = 1       # 眠三 (威胁)
        OPEN_TWO = 0.5  # 活二 (潜在威胁)
        
        # 空位置集合
        empty_positions = []
        for y in range(self.board_size):
            for x in range(self.board_size):
                if self.board[y][x] == Piece.EMPTY:
                    empty_positions.append((x, y))
        
        if not empty_positions:
            return None
        
        # 如果是第一步棋，优先选择天元或其附近位置
        if len(self.move_history) <= 1:
            center = self.board_size // 2
            center_positions = [(center, center)]
            for dx in [-1, 0, 1]:
                for dy in [-1, 0, 1]:
                    if dx == 0 and dy == 0:
                        continue
                    nx, ny = center + dx, center + dy
                    if 0 <= nx < self.board_size and 0 <= ny < self.board_size and self.board[ny][nx] == Piece.EMPTY:
                        center_positions.append((nx, ny))
            return random.choice(center_positions)
        
        # 对每个空位置进行评分
        best_move = None
        max_score = float('-inf')
        
        # 我方是白棋，对手是黑棋
        my_piece = Piece.WHITE
        opponent_piece = Piece.BLACK
        
        # 遍历所有空位置，计算每个位置的分数
        for x, y in empty_positions:
            # 检查是否有立即获胜的机会 (连五)
            self.board[y][x] = my_piece
            if self.check_win(x, y):
                self.board[y][x] = Piece.EMPTY
                return x, y  # 找到必胜位置，立即返回
            self.board[y][x] = Piece.EMPTY
            
            # 检查是否需要防守 (对手下一步可以获胜)
            self.board[y][x] = opponent_piece
            if self.check_win(x, y):
                self.board[y][x] = Piece.EMPTY
                return x, y  # 找到防守位置，立即返回
            self.board[y][x] = Piece.EMPTY
            
            # 计算该位置的综合分数
            my_score = self._evaluate_position(x, y, my_piece)
            opponent_score = self._evaluate_position(x, y, opponent_piece) * 0.9  # 稍微降低对手威胁权重
            position_score = my_score + opponent_score
            
            # 添加一些随机扰动，避免AI总是使用相同的策略
            position_score += random.uniform(0, 0.1)
            
            if position_score > max_score:
                max_score = position_score
                best_move = (x, y)
        
        return best_move
    
    def _evaluate_position(self, x, y, piece):
        """评估一个位置对于指定玩家的价值"""
        if self.board[y][x] != Piece.EMPTY:
            return 0  # 已经有棋子的位置无法落子
        
        # 临时模拟落子
        self.board[y][x] = piece
        
        # 初始分数，位于中心位置的分数更高
        score = 0
        center = self.board_size // 2
        distance_to_center = abs(x - center) + abs(y - center)
        score += (10 - distance_to_center) * 0.05  # 越靠近中心，基础分越高
        
        # 方向：横、竖、右下、右上
        directions = [(1, 0), (0, 1), (1, 1), (1, -1)]
        
        # 遍历四个方向
        for dx, dy in directions:
            # 获取当前方向的棋型
            line = self._get_line(x, y, dx, dy, piece)
            pattern_score = self._evaluate_pattern(line, piece)
            score += pattern_score
        
        # 恢复棋盘
        self.board[y][x] = Piece.EMPTY
        
        return score

    def _get_line(self, x, y, dx, dy, piece):
        """获取指定方向的棋子序列，用于棋型判断"""
        opponent = Piece.BLACK if piece == Piece.WHITE else Piece.WHITE
        line = []
        
        # 向一个方向延伸
        for i in range(-5, 6):  # 获取该位置周围5个位置的状态
            nx, ny = x + dx * i, y + dy * i
            if 0 <= nx < self.board_size and 0 <= ny < self.board_size:
                if i == 0:  # 当前位置
                    line.append(piece)  # 模拟落子
                else:
                    if self.board[ny][nx] == piece:
                        line.append(piece)
                    elif self.board[ny][nx] == opponent:
                        line.append(opponent)
                    else:
                        line.append(Piece.EMPTY)
            else:
                line.append(None)  # 超出边界
        
        return line

    def _evaluate_pattern(self, line, piece):
        """评估一个方向上的棋型价值"""
        opponent = Piece.BLACK if piece == Piece.WHITE else Piece.WHITE
        score = 0
        
        # 连五检测 (● ● ● ● ●)
        if self._check_consecutive(line, piece, 5):
            return 10000  # 必胜
        
        # 活四检测 (○ ● ● ● ● ○)
        if self._check_open_four(line, piece):
            return 1000  # 必胜
        
        # 冲四检测 (如 ○ ● ● ● ● ■ 或 ■ ● ● ● ● ○)
        if self._check_four(line, piece):
            return 100
        
        # 活三检测 (如 ○ ● ● ● ○)
        if self._check_open_three(line, piece):
            return 50
        
        # 眠三检测
        if self._check_three(line, piece):
            return 10
        
        # 活二检测
        if self._check_open_two(line, piece):
            return 5
        
        # 基础价值
        for i in range(len(line)):
            if line[i] == piece:
                score += 1
        
        return score

    def _check_consecutive(self, line, piece, count):
        """检查是否有count个连续棋子"""
        for i in range(len(line) - count + 1):
            if all(cell == piece for cell in line[i:i+count]):
                return True
        return False
    
    def _check_open_four(self, line, piece):
        """检查是否有活四"""
        for i in range(len(line) - 5):
            if (line[i] == Piece.EMPTY and 
                line[i+1] == piece and 
                line[i+2] == piece and 
                line[i+3] == piece and 
                line[i+4] == piece and 
                line[i+5] == Piece.EMPTY):
                return True
        return False
    
    def _check_four(self, line, piece):
        """检查是否有冲四"""
        # 边界冲四模式
        patterns = [
            [None, piece, piece, piece, piece, Piece.EMPTY],
            [Piece.EMPTY, piece, piece, piece, piece, None],
            [piece, piece, piece, piece, Piece.EMPTY],
            [piece, piece, piece, Piece.EMPTY, piece],
            [piece, piece, Piece.EMPTY, piece, piece],
            [piece, Piece.EMPTY, piece, piece, piece],
            [Piece.EMPTY, piece, piece, piece, piece]
        ]
        
        for pattern in patterns:
            for i in range(len(line) - len(pattern) + 1):
                match = True
                for j in range(len(pattern)):
                    if pattern[j] is not None and line[i+j] != pattern[j]:
                        match = False
                        break
                if match:
                    return True
        return False
    
    def _check_open_three(self, line, piece):
        """检查是否有活三"""
        patterns = [
            [Piece.EMPTY, piece, piece, piece, Piece.EMPTY],
            [Piece.EMPTY, piece, piece, Piece.EMPTY, piece, Piece.EMPTY],
            [Piece.EMPTY, piece, Piece.EMPTY, piece, piece, Piece.EMPTY]
        ]
        
        for pattern in patterns:
            for i in range(len(line) - len(pattern) + 1):
                match = True
                for j in range(len(pattern)):
                    if line[i+j] != pattern[j]:
                        match = False
                        break
                if match:
                    return True
        return False
    
    def _check_three(self, line, piece):
        """检查是否有眠三"""
        opponent = Piece.BLACK if piece == Piece.WHITE else Piece.WHITE
        patterns = [
            [opponent, piece, piece, piece, Piece.EMPTY, Piece.EMPTY],
            [Piece.EMPTY, Piece.EMPTY, piece, piece, piece, opponent],
            [opponent, piece, piece, Piece.EMPTY, piece, Piece.EMPTY],
            [Piece.EMPTY, piece, Piece.EMPTY, piece, piece, opponent],
            [opponent, piece, Piece.EMPTY, piece, piece, Piece.EMPTY],
            [Piece.EMPTY, piece, piece, Piece.EMPTY, piece, opponent]
        ]
        
        for pattern in patterns:
            for i in range(len(line) - len(pattern) + 1):
                match = True
                for j in range(len(pattern)):
                    if pattern[j] is not None and line[i+j] != pattern[j]:
                        match = False
                        break
                if match:
                    return True
        return False
    
    def _check_open_two(self, line, piece):
        """检查是否有活二"""
        patterns = [
            [Piece.EMPTY, Piece.EMPTY, piece, piece, Piece.EMPTY, Piece.EMPTY],
            [Piece.EMPTY, Piece.EMPTY, piece, Piece.EMPTY, piece, Piece.EMPTY, Piece.EMPTY],
            [Piece.EMPTY, piece, Piece.EMPTY, Piece.EMPTY, piece, Piece.EMPTY]
        ]
        
        for pattern in patterns:
            for i in range(len(line) - len(pattern) + 1):
                match = True
                for j in range(len(pattern)):
                    if pattern[j] is not None and line[i+j] != pattern[j]:
                        match = False
                        break
                if match:
                    return True
        return False

    def ai_move(self):
        """AI落子功能分发器，根据选择的算法调用不同的AI实现"""
        if self.ai_algorithm == "traditional":
            return self.traditional_ai_move()
        else:
            # 原始的基于神经网络的AI实现
            if self.game_over or self.current_player != Piece.WHITE:  # 假设AI执白棋
                return
            
            try:
                # 直接加载模型，不使用GomokuEnv
                model_path = os.path.join("gomoku_rl-main", "gomoku_rl-main", "pretrained_models", "15_15", "ppo", "1.pt")
                
                # 将当前棋盘状态转换为模型输入格式
                # 创建特征平面：黑子位置(1)、白子位置(1)、当前玩家(1)
                board_state = np.zeros((3, self.board_size, self.board_size), dtype=np.float32)
                
                # 填充黑子和白子的位置
                for y in range(self.board_size):
                    for x in range(self.board_size):
                        if self.board[y][x] == Piece.BLACK:
                            board_state[0, y, x] = 1.0  # 黑子位置
                        elif self.board[y][x] == Piece.WHITE:
                            board_state[1, y, x] = 1.0  # 白子位置
                
                # 当前玩家是白棋(AI)
                board_state[2, :, :] = 1.0  # 表示当前玩家是白棋
                
                # 转换为torch张量
                state_tensor = torch.from_numpy(board_state)
                
                # 创建一个简单的DQN网络类，与原模型结构匹配
                class SimpleDQN(torch.nn.Module):
                    def __init__(self, board_size=15):
                        super().__init__()
                        self.board_size = board_size
                        self.conv1 = torch.nn.Conv2d(3, 32, kernel_size=3, padding=1)
                        self.conv2 = torch.nn.Conv2d(32, 64, kernel_size=3, padding=1)
                        self.conv3 = torch.nn.Conv2d(64, 128, kernel_size=3, padding=1)
                        self.fc = torch.nn.Linear(128 * board_size * board_size, board_size * board_size)
                        
                    def forward(self, x):
                        x = torch.relu(self.conv1(x))
                        x = torch.relu(self.conv2(x))
                        x = torch.relu(self.conv3(x))
                        x = x.view(-1, 128 * self.board_size * self.board_size)
                        return self.fc(x)
                
                # 创建模型并加载权重
                model = SimpleDQN(board_size=self.board_size)
                model.load_state_dict(torch.load(model_path, map_location="cpu"))
                model.eval()
                
                # 获取AI的动作
                with torch.no_grad():
                    q_values = model(state_tensor.unsqueeze(0))
                    
                    # 创建合法动作掩码（只能在空位置落子）
                    legal_mask = torch.ones_like(q_values) * float('-inf')
                    for y in range(self.board_size):
                        for x in range(self.board_size):
                            if self.board[y][x] == Piece.EMPTY:
                                idx = y * self.board_size + x
                                legal_mask[0, idx] = 0
                    
                    # 应用掩码并获取最佳动作
                    masked_q_values = q_values + legal_mask
                    action = masked_q_values.argmax(dim=-1).item()
                    
                    # 将一维动作转换为二维坐标
                    board_y, board_x = divmod(action, self.board_size)
                
                # 记录AI的落子
                self.move_history.append((board_x, board_y, self.current_player))
                
                # 更新棋盘
                self.board[board_y][board_x] = Piece.WHITE
                
                # 播放落子音效
                if self.down_sound:
                    self.down_sound.play()
                
                # 重置计时器
                self.white_time_left = self.turn_time_limit
                self.last_time_update = pygame.time.get_ticks()
                
                # 检查AI是否获胜
                if self.check_win(board_x, board_y):
                    self.game_over = True
                    self.winner = Piece.WHITE
                    if self.lose_sound:
                        self.lose_sound.play()
                else:
                    # 切换到玩家回合
                    self.current_player = Piece.BLACK
                
            except Exception as e:
                print(f"AI落子出错: {e}")
                import traceback
                traceback.print_exc()
                
                # 如果AI出错，随机选择一个合法位置
                print("使用随机落子策略作为备选")
                empty_positions = []
                for y in range(self.board_size):
                    for x in range(self.board_size):
                        if self.board[y][x] == Piece.EMPTY:
                            empty_positions.append((x, y))
                
                if empty_positions:
                    import random
                    board_x, board_y = random.choice(empty_positions)
                    
                    # 记录AI的随机落子
                    self.move_history.append((board_x, board_y, self.current_player))
                    
                    # 更新棋盘
                    self.board[board_y][board_x] = Piece.WHITE
                    
                    # 播放落子音效
                    if self.down_sound:
                        self.down_sound.play()
                    
                    # 重置计时器
                    self.white_time_left = self.turn_time_limit
                    self.last_time_update = pygame.time.get_ticks()
                    
                    # 检查AI是否获胜
                    if self.check_win(board_x, board_y):
                        self.game_over = True
                        self.winner = Piece.WHITE
                        if self.lose_sound:
                            self.lose_sound.play()
                    else:
                        # 切换到玩家回合
                        self.current_player = Piece.BLACK

    def handle_event(self, event):
        if event.type == pygame.MOUSEBUTTONDOWN:
            if event.button == 1:  # 左键点击
                x, y = event.pos
                print(f"点击位置: x={x}, y={y}")
                
                # 检查是否点击了返回菜单按钮
                if self.back_button_rect.collidepoint(x, y):
                    # 返回菜单并恢复原窗口大小
                    self.game.return_to_menu()
                    return
                
                # 检查是否点击了悔棋按钮
                if self.undo_button_rect.collidepoint(x, y):
                    self.undo_move()
                    return
                
                # 只有在游戏未结束且是玩家回合时才处理棋盘点击
                elif not self.game_over:
                    # 检查是否点击在棋盘区域内
                    if self.board_rect.collidepoint(x, y):
                        print(f"点击在棋盘区域内")
                        # 计算棋盘坐标
                        board_x = (x - self.board_x + self.cell_size // 2) // self.cell_size
                        board_y = (y - self.board_y + self.cell_size // 2) // self.cell_size
                        
                        # 确保坐标在有效范围内
                        if 0 <= board_x < self.board_size and 0 <= board_y < self.board_size:
                            print(f"有效的棋盘坐标: x={board_x}, y={board_y}")
                            if self.game_mode == "local":
                                if self.board[board_y][board_x] == Piece.EMPTY:
                                    # 记录当前落子
                                    self.move_history.append((board_x, board_y, self.current_player))
                                    
                                    # 更新棋盘
                                    self.board[board_y][board_x] = self.current_player
                                    print(f"落子: {board_x}, {board_y}, 玩家: {self.current_player}")
                                    cx = self.board_x + board_x * self.cell_size
                                    cy = self.board_y + board_y * self.cell_size
                                    
                                    # 播放落子音效
                                    if self.down_sound:
                                        self.down_sound.play()
                                    
                                    # 重置当前玩家的计时器
                                    if self.current_player == Piece.BLACK:
                                        self.black_time_left = self.turn_time_limit
                                    else:
                                        self.white_time_left = self.turn_time_limit
                                    self.last_time_update = pygame.time.get_ticks()
                                    
                                    if self.check_win(board_x, board_y):
                                        self.game_over = True
                                        self.winner = self.current_player
                                        if self.win_sound:
                                            self.win_sound.play()
                                    else:
                                        if self.current_player == Piece.BLACK:
                                            self.current_player = Piece.WHITE
                                        else:
                                            self.current_player = Piece.BLACK
                                else:
                                    print(f"该位置已有棋子")

                            elif self.game_mode == "ai":
                                if self.board[board_y][board_x] == Piece.EMPTY:
                                    # 记录玩家落子
                                    self.move_history.append((board_x, board_y, self.current_player))
                                    
                                    # 更新棋盘
                                    self.board[board_y][board_x] = self.current_player
                                    
                                    # 播放落子音效
                                    if self.down_sound:
                                        self.down_sound.play()
                                    
                                    # 重置计时器
                                    self.black_time_left = self.turn_time_limit
                                    self.last_time_update = pygame.time.get_ticks()
                                    
                                    # 检查玩家是否获胜
                                    if self.check_win(board_x, board_y):
                                        self.game_over = True
                                        self.winner = Piece.BLACK
                                        if self.win_sound:
                                            self.win_sound.play()
                                    else:
                                        # 切换到AI回合
                                        self.current_player = Piece.WHITE
                                        # AI落子
                                        self.ai_move()
                        else:
                            print(f"无效的棋盘坐标: x={board_x}, y={board_y}")
                    else:
                        print(f"点击在棋盘区域外")
    
    def check_win(self, x, y):
        """检查是否有五子连珠"""
        player = self.board[y][x]
        directions = [(1, 0), (0, 1), (1, 1), (1, -1)]  # 横、竖、右下、右上
        
        for dx, dy in directions:
            count = 1  # 当前位置已经有一个棋子
            
            # 正向检查
            for i in range(1, 5):
                nx, ny = x + dx * i, y + dy * i
                if 0 <= nx < self.board_size and 0 <= ny < self.board_size and self.board[ny][nx] == player:
                    count += 1
                else:
                    break
            
            # 反向检查
            for i in range(1, 5):
                nx, ny = x - dx * i, y - dy * i
                if 0 <= nx < self.board_size and 0 <= ny < self.board_size and self.board[ny][nx] == player:
                    count += 1
                else:
                    break
            
            if count >= 5:
                return True
        
        return False
        
    def record_game_result(self):
        """记录游戏结果到排行榜"""
        if self.result_recorded or not self.db_manager:
            return
            
        try:
            # 根据游戏模式和获胜者更新排行榜
            if self.game_mode == "local":
                # 本地对战模式，黑棋为玩家1，白棋为玩家2
                if self.winner == Piece.BLACK:
                    # 玩家1获胜
                    self.db_manager.update_ranking(self.username, "win")
                    print(f"记录玩家 {self.username} 胜利")
                else:
                    # 玩家2获胜
                    self.db_manager.update_ranking(self.username, "loss")
                    print(f"记录玩家 {self.username} 失败")
            elif self.game_mode == "ai":
                # AI对战模式，玩家总是黑棋
                if self.winner == Piece.BLACK:
                    # 玩家获胜
                    self.db_manager.update_ranking(self.username, "win")
                    print(f"记录玩家 {self.username} 战胜AI")
                else:
                    # AI获胜
                    self.db_manager.update_ranking(self.username, "loss")
                    print(f"记录玩家 {self.username} 被AI击败")
            
            self.result_recorded = True
        except Exception as e:
            print(f"记录游戏结果时出错: {e}")
    
    def render(self):
        # 更新计时器
        self.update_timer()
        
        # 填充背景
        self.screen.fill(self.light_gray)
        
        # 绘制游戏标题
        try:
            title_font = pygame.font.Font(self.font_path, 48)
        except:
            title_font = pygame.font.SysFont("simsun", 48)
        title_text = title_font.render("五子棋", True, (80, 80, 80))
        title_rect = title_text.get_rect(centerx=self.width//2, top=15)
        self.screen.blit(title_text, title_rect)
        
        # 创建信息面板背景
        info_panel_rect = pygame.Rect(20, 20, 200, 160)
        pygame.draw.rect(self.screen, (245, 245, 245), info_panel_rect, 0, 12)
        pygame.draw.rect(self.screen, self.gray, info_panel_rect, 2, 12)
        
        # 绘制用户信息 - 调整位置，适应更小的信息框
        user_text = self.title_font.render(f"玩家: {self.username}", True, self.black)
        self.screen.blit(user_text, (35, 40))
        
        # 绘制游戏模式信息 - 调整位置，适应更小的信息框
        mode_text = self.info_font.render(self.mode_text, True, self.apple_blue)
        self.screen.blit(mode_text, (35, 95))
        
        # 绘制当前玩家信息 - 调整位置，适应更小的信息框
        player_text = self.info_font.render(
            f"当前回合: {'黑棋' if self.current_player == Piece.BLACK else '白棋'}", 
            True, 
            self.black
        )
        self.screen.blit(player_text, (35, 145))
        
        # 绘制计时器 - 移到左上角
        # 黑棋计时器
        black_timer_rect = pygame.Rect(20, 220, 120, 50)
        pygame.draw.rect(self.screen, (50, 50, 50), black_timer_rect, 0, 8)
        black_timer_text = self.timer_font.render(f"{int(self.black_time_left)}秒", True, self.white)
        black_timer_text_rect = black_timer_text.get_rect(center=black_timer_rect.center)
        self.screen.blit(black_timer_text, black_timer_text_rect)
        
        # 白棋计时器
        white_timer_rect = pygame.Rect(20, 320, 120, 50)
        pygame.draw.rect(self.screen, self.white, white_timer_rect, 0, 8)
        white_timer_text = self.timer_font.render(f"{int(self.white_time_left)}秒", True, self.black)
        white_timer_text_rect = white_timer_text.get_rect(center=white_timer_rect.center)
        self.screen.blit(white_timer_text, white_timer_text_rect)
        
        # 绘制计时器标签
        black_label = self.info_font.render("黑棋时间:", True, self.black)
        black_label_rect = black_label.get_rect(bottom=black_timer_rect.top - 5, centerx=black_timer_rect.centerx)
        self.screen.blit(black_label, black_label_rect)
        
        white_label = self.info_font.render("白棋时间:", True, self.black)
        white_label_rect = white_label.get_rect(bottom=white_timer_rect.top - 5, centerx=white_timer_rect.centerx)
        self.screen.blit(white_label, white_label_rect)
        
        # 绘制返回菜单按钮 - 调整样式
        mouse_pos = pygame.mouse.get_pos()
        button_color = self.apple_light_blue if self.back_button_rect.collidepoint(mouse_pos) else self.apple_blue
        pygame.draw.rect(self.screen, button_color, self.back_button_rect, 0, 8)
        
        # 使用稍小的字体绘制按钮文本
        try:
            button_font = pygame.font.Font(self.font_path, 22)
        except:
            button_font = pygame.font.SysFont("simsun", 22)
        back_text = button_font.render(self.back_button_text, True, self.white)
        back_text_rect = back_text.get_rect(center=self.back_button_rect.center)
        self.screen.blit(back_text, back_text_rect)
        
        # 绘制悔棋按钮
        button_color = self.apple_light_blue if self.undo_button_rect.collidepoint(mouse_pos) else self.apple_blue
        pygame.draw.rect(self.screen, button_color, self.undo_button_rect, 0, 8)
        undo_text = button_font.render(self.undo_button_text, True, self.white)
        undo_text_rect = undo_text.get_rect(center=self.undo_button_rect.center)
        self.screen.blit(undo_text, undo_text_rect)
        
        # 绘制棋盘背景
        pygame.draw.rect(
            self.screen, 
            self.board_color, 
            self.board_rect
        )
        
        # 绘制棋盘网格
        for i in range(self.board_size):
            # 横线
            thickness = 5 if i == 0 or i == (self.board_size - 1) else 2
            pygame.draw.line(
                self.screen,
                self.black,
                (self.board_x, self.board_y + i * self.cell_size),
                (self.board_x + self.board_width, self.board_y + i * self.cell_size),
                thickness
            )
            # 竖线
            pygame.draw.line(
                self.screen,
                self.black,
                (self.board_x + i * self.cell_size, self.board_y),
                (self.board_x + i * self.cell_size, self.board_y + self.board_width),
                thickness
            )
        
        # 绘制棋盘上的天元
        star_points = [(3, 3), (3, 11), (7, 7), (11, 3), (11, 11)]
        for x, y in star_points:
            pygame.draw.circle(
                self.screen,
                self.black,
                (self.board_x + x * self.cell_size, self.board_y + y * self.cell_size),
                10
            )
        
        # 绘制棋子
        for y in range(self.board_size):
            for x in range(self.board_size):
                if self.board[y][x] != Piece.EMPTY:
                    piece_x = self.board_x + x * self.cell_size
                    piece_y = self.board_y + y * self.cell_size
                    
                    if self.board[y][x] == Piece.BLACK:  # 黑棋
                        piece_rect = self.black_piece.get_rect(center=(piece_x, piece_y))
                        self.screen.blit(self.black_piece, piece_rect)
                    else:  # 白棋
                        piece_rect = self.white_piece.get_rect(center=(piece_x, piece_y))
                        self.screen.blit(self.white_piece, piece_rect)
                       
        
        # 如果游戏结束，显示获胜信息
        if self.game_over:
            winner_text = "黑棋获胜！" if self.winner == Piece.BLACK else "白棋获胜！"
            
            # 创建更醒目的胜利信息面板
            panel_width = 300
            panel_height = 80
            panel_rect = pygame.Rect(
                (self.width - panel_width) // 2,
                (self.height - panel_height) // 2,
                panel_width,
                panel_height
            )
            
            # 不透明背景
            background_color = self.apple_blue if self.winner == Piece.BLACK else (50, 50, 50)
            pygame.draw.rect(self.screen, background_color, panel_rect, 0, 10)
            
            # 绘制边框
            pygame.draw.rect(self.screen, self.white, panel_rect, 2, 10)
            
            # 绘制文本
            text = self.title_font.render(winner_text, True, self.white)
            text_rect = text.get_rect(center=panel_rect.center)
            self.screen.blit(text, text_rect)
            
            # 如果还未记录结果，记录游戏结果
            if not self.result_recorded:
                self.record_game_result()
        
        # 绘制底部版权信息
        try:
            footer_font = pygame.font.Font(self.font_path, 18)
        except:
            footer_font = pygame.font.SysFont("simsun", 18)
        footer_text = footer_font.render("© 2023 五子棋游戏", True, (150, 150, 150))
        footer_rect = footer_text.get_rect(centerx=self.width//2, bottom=self.height-15)
        self.screen.blit(footer_text, footer_rect) 

    def undo_move(self):
        """悔棋功能"""
        if not self.move_history or self.game_over:
            return False
        
        # 获取最后一步落子
        last_x, last_y, last_player = self.move_history.pop()
        
        # 清除棋子
        self.board[last_y][last_x] = Piece.EMPTY
        
        # 如果是AI模式，需要同时撤销AI或对手的落子
        if self.game_mode in ["ai"] and len(self.move_history) > 0:
            ai_x, ai_y, ai_player = self.move_history.pop()
            self.board[ai_y][ai_x] = Piece.EMPTY
            self.current_player = Piece.BLACK
        else:
            # 恢复当前玩家
            self.current_player = last_player
        # 重置计时器
        if self.current_player == Piece.BLACK:
            self.black_time_left = self.turn_time_limit
        else:
            self.white_time_left = self.turn_time_limit
        self.last_time_update = pygame.time.get_ticks()
        
        return True
    
    def update_timer(self):
        """更新计时器"""
        if self.game_over:
            return
        
        current_time = pygame.time.get_ticks()
        elapsed = (current_time - self.last_time_update) / 1000.0  # 转换为秒
        self.last_time_update = current_time
        
        # 更新当前玩家的剩余时间
        if self.current_player == Piece.BLACK:
            self.black_time_left -= elapsed
            if self.black_time_left <= 0:
                self.black_time_left = 0
                self.game_over = True
                self.winner = Piece.WHITE
                print("黑棋超时，白棋获胜")
        else:
            self.white_time_left -= elapsed
            if self.white_time_left <= 0:
                self.white_time_left = 0
                self.game_over = True
                self.winner = Piece.BLACK
                print("白棋超时，黑棋获胜") 